package com.yy.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.http.HttpRequest;
import cn.hutool.http.HttpResponse;
import cn.hutool.http.HttpUtil;
import cn.hutool.http.Method;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.qcloud.cos.COSClient;
import com.qcloud.cos.ClientConfig;
import com.qcloud.cos.auth.BasicCOSCredentials;
import com.qcloud.cos.auth.COSCredentials;
import com.qcloud.cos.http.HttpProtocol;
import com.qcloud.cos.model.ciModel.image.GenerateQrcodeRequest;
import com.qcloud.cos.region.Region;
import com.yy.domain.*;
import com.yy.dao.AppointmentTasksMapper;
import com.yy.dto.*;
import com.yy.enums.TaskStatus;
import com.yy.service.*;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.yy.utils.*;
import com.yy.vo.AppointmentTasksPageVO;
import com.yy.vo.AppointmentTasksVO;
import com.yy.vo.LoginVO;
import com.yy.vo.ScheduleRequestVO;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.stream.Collectors;

/**
 * <p>
 * 服务实现类
 * </p>
 *
 * @author 姚欣宏
 * @since 2023-07-06
 */
@Slf4j
@Service
public class AppointmentTasksServiceImpl extends ServiceImpl<AppointmentTasksMapper, AppointmentTasksDO> implements AppointmentTasksService {
    private final PatientService patientService;
    private final DepartmentCategoryService departmentCategoryService;
    private final DoctorService doctorService;
    private final BusinessTagItemService businessTagItemService;
    private final AppointmentScheduleService appointmentScheduleService;
    private final ImageDataService imageDataService;
    private final ApiLogService apiLogService;
    private static final String SECRET_ID = "AKID40kJfokU1KQK4bu1DCzXt21nNsDOPQQG";
    private static final String SECRET_KEY = "jbJuJUUK3e3HLG0Yu6A4nLiw0zoSwHST";
    private static final String BUCKET_NAME = "lkang-1316488626";
    private static final String APP_CODE = "HXGYAPP";
    @Value("${secondsValue}")
    private Integer SECONDS;
    private static final String HOSPITAL_CODE = "HID0101";

    public AppointmentTasksServiceImpl(PatientService patientService, DepartmentCategoryService departmentCategoryService, DoctorService doctorService, BusinessTagItemService businessTagItemService, AppointmentScheduleService appointmentScheduleService, ImageDataService imageDataService, ApiLogService apiLogService) {
        this.patientService = patientService;
        this.departmentCategoryService = departmentCategoryService;
        this.doctorService = doctorService;
        this.businessTagItemService = businessTagItemService;
        this.appointmentScheduleService = appointmentScheduleService;
        this.imageDataService = imageDataService;
        this.apiLogService = apiLogService;
    }

    @Override
    public Integer appointmentTasks(AppointmentTasksVO appointmentTasksVO) {
        //登录华医通获取token
        LoginVO loginVO = ConvertUtils.beanCopy(appointmentTasksVO, LoginVO.class);
        ApiLogDO apiLogDO = addApiLog("华医通登陆", "http://guahao.wchscu.cn/login/login", "authKey=" + loginVO.getAuthKey() + "&authCode=" + loginVO.getAuthCode() + "&phone=" + loginVO.getAppointmentPhone());
        String token = login(loginVO);
        if (StringUtils.isNoneBlank(token)) {
            AppointmentTasksDO appointmentTasksDO = ConvertUtils.beanCopy(appointmentTasksVO, AppointmentTasksDO.class);
            appointmentTasksDO.setToken(token);
            appointmentTasksDO.setCreateTime(new Date());
            appointmentTasksDO.setTaskStatus(TaskStatus.PENDING_CONFIGURATION.getCode());
            appointmentTasksDO.setStatus(null);
            save(appointmentTasksDO);
            updateApiLog(appointmentTasksDO, apiLogDO, token);
            return appointmentTasksDO.getId();
        } else {
            return 0;
        }
    }

    private String login(LoginVO loginVO) {
        String token = "";
        String url = "http://guahao.wchscu.cn/login/login";
        String data = "authKey=" + loginVO.getAuthKey() + "&authCode=" + loginVO.getAuthCode() + "&phone=" + loginVO.getAppointmentPhone();
        log.info("data:" + data);
        HttpRequest request = HttpUtil.createRequest(Method.POST, url);
        request.header("Connection", "keep-alive").header("Origin", "http://guahao.wchscu.cn").header("User-Agent", "Mozilla/5.0 (Macintosh; Intel Mac OS X -1_0_0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36").header("token", "eyJhbGciOiJIUzI1NiJ9.eyJqdGkiOiIyNTI0Mzk2QXBIZFNQT3NwZVVXNmpRSXdYbGZUUnNXcFcxVEpnZldhWTBUV3hWNnc5ZFoiLCJpYXQiOjE2NDY5MDIxMDUsInN1YiI6IntcInVzZXJJZFwiOlwiMjUyNDM5NlwiLFwiYWNjb3VudElkXCI6XCIyOTgwMzMzXCIsXCJ1c2VyVHlwZVwiOjAsXCJhcHBDb2RlXCI6XCJIWEdZQVBQXCIsXCJjaGFubmVsQ29kZVwiOlwiUEFUSUVOVF9BTkRST0lEXCIsXCJkZXZpY2VudW1iZXJcIjpcIkFwSGRTUE9zcGVVVzZqUUl3WGxmVFJzV3BXMVRKZ2ZXYVkwVFd4VjZ3OWRaXCIsXCJkZXZpY2VUeXBlXCI6XCJBUFBcIixcImFjY291bnROb1wiOlwiMTgzMjgwMDM0MzNcIixcIm5hbWVcIjpudWxsLFwiZG9jdG9ySWRcIjpudWxsLFwib3JnYW5Db2RlXCI6bnVsbH0iLCJleHAiOjE2NDk0OTQxMDV9.4oF1kMDRTHUXyZX0A6ihH8VemRxDNAyW7ynP-wPoyaQ***HXGYAPP").header("Content-Type", "application/x-www-form-urlencoded;application/json;charset=UTF-8;").header("Accept", "*/*").header("Referer", "http://guahao.wchscu.cn/file/h5/index.html").header("Accept-Encoding", "gzip, deflate").header("Accept-Language", "zh-CN,zh;q=0.9").header("Cookie", "acw_tc=781bad2316886240948188586e511e2b80c89998fb3a2a62e2492d387dfbde").body(data);
        HttpResponse response = request.execute();
        if (response.isOk()) {
            String body = response.body();
            log.info("请求成功：" + body);
            LoginDTO result = JSON.parseObject(body, LoginDTO.class);
            token = result.getData().getToken();
        } else {
            log.info("请求失败，状态码：" + response.getStatus());
        }
        return token;
    }


    @Override
    public PageInfo<AppointmentTasksDO> selectAppointmentTsks(AppointmentTasksPageVO appointmentTasksPageVO) {
        PageHelper.startPage(appointmentTasksPageVO.getPageNum(), appointmentTasksPageVO.getPageSize());
        QueryWrapper<AppointmentTasksDO> wrapper = new QueryWrapper<>();
        wrapper.eq(StringUtils.isNotBlank(appointmentTasksPageVO.getAppointmentDate()), "appointment_date", appointmentTasksPageVO.getAppointmentDate()).eq(StringUtils.isNotBlank(appointmentTasksPageVO.getServer()), "server", appointmentTasksPageVO.getServer()).like(StringUtils.isNotBlank(appointmentTasksPageVO.getAppointmentPhone()), "appointment_phone", appointmentTasksPageVO.getAppointmentPhone()).like(StringUtils.isNotBlank(appointmentTasksPageVO.getDoctor()), "doc_name", appointmentTasksPageVO.getDoctor()).like(StringUtils.isNotBlank(appointmentTasksPageVO.getProcessor()), "processor", appointmentTasksPageVO.getProcessor()).orderByDesc("id");
        List<AppointmentTasksDO> appointmentTasksDOList = list(wrapper);
        PageInfo<AppointmentTasksDO> pageInfo = new PageInfo(appointmentTasksDOList);
        return pageInfo;
    }

    @Override
    public Integer configurationAppointmentTasks(AppointmentTasksVO appointmentTasksVO) {
        AppointmentTasksDO appointmentTasksDO = getById(appointmentTasksVO.getId());
        BeanUtil.copyProperties(appointmentTasksVO, appointmentTasksDO);
        int index = appointmentTasksVO.getDoctorId().indexOf("--");
        if (index != -1) {
            appointmentTasksDO.setDoctorId(appointmentTasksVO.getDoctorId().substring(0, index));
        }
        try {
            appointmentTasksDO.setAppointmentDate(new SimpleDateFormat("yyyy-MM-dd").parse(appointmentTasksVO.getAppointmentDate()));
            appointmentTasksDO.setTreatmentDate(new SimpleDateFormat("yyyy-MM-dd").parse(appointmentTasksVO.getTreatmentDate()));
        } catch (ParseException e) {
            throw new RuntimeException(e);
        }
        appointmentTasksDO.setTaskStatus(TaskStatus.PENDING_SCHEDULE_RETRIEVAL.getCode());
        appointmentTasksDO.setUpdateTime(new Date());
        updateById(appointmentTasksDO);
        return appointmentTasksDO.getId();
    }

    @Override
    public List<UserCardListDTO> cardlist(Integer id) {
        AppointmentTasksDO appointmentTasksDO = getById(id);
        String token = appointmentTasksDO.getToken();
        JSONObject json = new JSONObject();
        json.put("appCode", "HXGYAPP");
        json.put("channelCode", "HXGYAPP");
        json.put("loading", false);
        json.put("organCode", "HID0101");
        String url = "https://hxgyapiv2.cd120.info/cloud/hosplatcustomer/cardservice/cardlist";
        //ApiLogDO apiLogDO = addApiLog("华医通就诊卡列表", url, json.toJSONString());
        HttpResponse response = HutoolUtil.sendPost(url, token, json);
        CardListDTO result = HutoolUtil.parseJsonResponse(response, CardListDTO.class);
        List<UserCardListDTO> cardListDTOS = result.getData().getUserCardList();
        if (CollUtil.isNotEmpty(cardListDTOS)) {
            cardListDTOS.forEach(cardListDTO -> {
                String cardId = cardListDTO.getCardId();
                QueryWrapper<PatientDO> wrapper = new QueryWrapper<>();
                wrapper.eq("card_id", cardId);
                PatientDO patientDO = patientService.getOne(wrapper);
                if (Objects.isNull(patientDO)) {
                    patientDO = ConvertUtils.beanCopy(cardListDTO, PatientDO.class);
                    patientService.save(patientDO);
                }
            });
        }
        //updateApiLog(appointmentTasksDO, apiLogDO, response.body());
        return cardListDTOS;
    }

    @Override
    public List<DeptDTO> selFirstDept(Integer id) {
        AppointmentTasksDO appointmentTasksDO = getById(id);
        String token = appointmentTasksDO.getToken();
        JSONObject json = new JSONObject();
        json.put("appCode", "HXGYAPP");
        json.put("appointmentType", "1");
        json.put("channelCode", "PATIENT_IOS");
        json.put("hospitalArea", "HID0101");
        json.put("hospitalCode", "HID0101");
        String url = "https://hytapiv2.cd120.com/cloud/hosplatcustomer/call/appointment/dept/selFirstDept";
        //ApiLogDO apiLogDO = addApiLog("华医通华西园区科室列表", url, json.toJSONString());
        HttpResponse response = HutoolUtil.sendPost(url, token, json);
        DeptListDTO result = HutoolUtil.parseJsonResponse(response, DeptListDTO.class);
        List<DeptDTO> deptDTOS = result.getData();
        if (CollUtil.isNotEmpty(deptDTOS)) {
            deptDTOS.forEach(deptDTO -> {
                String deptCategoryCode = deptDTO.getDeptCategoryCode();
                QueryWrapper<DepartmentCategoryDO> wrapper = new QueryWrapper<>();
                wrapper.eq("dept_category_code", deptCategoryCode);
                DepartmentCategoryDO departmentCategoryDO = departmentCategoryService.getOne(wrapper);
                if (Objects.isNull(departmentCategoryDO)) {
                    departmentCategoryDO = ConvertUtils.beanCopy(deptDTO, DepartmentCategoryDO.class);
                    departmentCategoryService.save(departmentCategoryDO);
                }
            });
        }
        //updateApiLog(appointmentTasksDO, apiLogDO, response.body());
        return deptDTOS;
    }

    @Override
    public List<DoctorDTO> selDoctorListByMoreTerm(Integer id, String deptCategoryCode) {
        AppointmentTasksDO appointmentTasksDO = getById(id);
        String token = appointmentTasksDO.getToken();
        JSONObject json = new JSONObject();
        String timestamp = String.valueOf(System.currentTimeMillis() / 1000);
        String encryptedData = EncryptionUtil.encrypt(timestamp);
        log.info("Encrypted data: " + encryptedData);
        json.put("deptCategoryCode", deptCategoryCode);
        json.put("hospitalAreaCode", "HID0101");
        json.put("hospitalCode", "HID0101");
        json.put("haveNo", "2");
        json.put("channelCode", "PATIENT_IOS");
        json.put("appointmentType", "1");
        json.put("appCode", "HXGYAPP");
        json.put("keyWordEnumType", "0");
        json.put("timestamp", timestamp);
        json.put("encrypt", encryptedData);
        log.info("请求参数：" + json.toJSONString());
        String url = "https://hytapiv2.cd120.com/cloud/hosplatcustomer/call/appointment/doctorListModel/selDoctorListByMoreTerm";
        HttpResponse response = HutoolUtil.sendPost(url, token, json);
        DoctorListDTO result = HutoolUtil.parseJsonResponse(response, DoctorListDTO.class);
        List<DoctorDTO> doctorDTOS = result.getData();
        if (CollUtil.isNotEmpty(doctorDTOS)) {
            doctorDTOS.forEach(doctorDTO -> {
                String doctorId = doctorDTO.getDoctorId();
                String deptCode = doctorDTO.getDeptCode();
                QueryWrapper<DoctorDO> wrapper = new QueryWrapper<>();
                wrapper.eq("doctor_id", doctorId);
                wrapper.eq("dept_code", deptCode);
                DoctorDO doctorDO = doctorService.getOne(wrapper);
                if (Objects.isNull(doctorDO)) {
                    doctorDO = ConvertUtils.beanCopy(doctorDTO, DoctorDO.class);
                    doctorService.save(doctorDO);
                    List<BusinessTagItemRespVoListDTO> businessTagItemRespVoListDTOS = doctorDTO.getBusinessTagItemRespVoList();
                    if (CollUtil.isNotEmpty(businessTagItemRespVoListDTOS)) {
                        businessTagItemRespVoListDTOS.forEach(businessTagItemRespVoListDTO -> {
                            BusinessTagItemDO businessTagItemDO = ConvertUtils.beanCopy(businessTagItemRespVoListDTO, BusinessTagItemDO.class);
                            businessTagItemDO.setDoctorId(doctorId);
                            businessTagItemDO.setDeptCode(deptCode);
                            businessTagItemService.save(businessTagItemDO);
                        });
                    }
                }
            });
        }
        return doctorDTOS;
    }

    @Override
    public String sureAppointment(Integer id) {
        AppointmentTasksDO appointmentTasksDO = getById(id);
        QueryWrapper<ImageDataDO> wrapper = new QueryWrapper<>();
        wrapper.eq("task_id", id);
        wrapper.eq("is_used", 0);
        wrapper.orderByDesc("id");
        List<ImageDataDO> imageDataDOS = imageDataService.list(wrapper);
        log.info("华医通提交预约-手动:" + id);
        if (CollUtil.isNotEmpty(imageDataDOS)) {
            ImageDataDO imageDataDO = imageDataDOS.stream().findAny().get();
            imageDataDO.setIsUsed(1);
            imageDataService.updateById(imageDataDO);
            String token = appointmentTasksDO.getToken();
            JSONObject json = new JSONObject();
            json.put("appCode", "HXGYAPP");
            json.put("appointmentType", "1");
            json.put("cardId", appointmentTasksDO.getCardId());
            json.put("channelCode", "PATIENT_IOS");
            json.put("hospitalCode", "HID0101");
            json.put("sysScheduleId", appointmentTasksDO.getSysScheduleId());
            json.put("type", "WEB");
            json.put("verifyCode", imageDataDO.getImageCode());
            json.put("channelElderCode", "PATIENT_IOS");
            json.put("imageId", imageDataDO.getBizSeq());
            json.put("encrypt", SecretUtil.encrypt(SecretUtil.getImageId(imageDataDO.getBizSeq())));
            log.info(id + "请求参数：" + json.toJSONString());
            String url = "https://hytapiv2.cd120.com/cloud/hosplatcustomer/call/appointment/appointmentModel/sureAppointment";
            ApiLogDO apiLogDO = addApiLog(appointmentTasksDO, "华医通提交预约-手动", url, json.toJSONString());
            ExecutorService executorService = Executors.newSingleThreadExecutor();
            executorService.execute(() -> {
                try {
                    HttpResponse response = HutoolUtil.sendPost(url, token, json);
                    SureAppointmentDTO result = HutoolUtil.parseJsonResponse(response, SureAppointmentDTO.class);
                    // 处理返回结果
                    log.info("返回参数：" + result);
                    updateApiLog(appointmentTasksDO, apiLogDO, response.body());
                } catch (Exception e) {
                    // 处理异常
                    updateApiLog(appointmentTasksDO, apiLogDO, e.getMessage());
                    log.info("发生异常：" + e.getMessage());
                }
            });
            executorService.shutdown();
            appointmentTasksDO.setTaskStatus(TaskStatus.APPOINTMENT_FAILED.getCode());
            appointmentTasksDO.setUpdateTime(new Date());
            updateById(appointmentTasksDO);
            return "预约执行成功";
        } else {
            return "请先获取验证码";
        }
    }

    @Override
    public List<ContentDTO> selAppointmentRecord(Integer id) {
        AppointmentTasksDO appointmentTasksDO = getById(id);
        String token = appointmentTasksDO.getToken();
        JSONObject json = new JSONObject();
        JSONObject query = new JSONObject();
        json.put("asc", "true");
        json.put("pageNum", 1);
        json.put("pageSize", 200);
        query.put("appCode", "HXGYAPP");
        query.put("channelCode", "PATIENT_IOS");
        query.put("hospitalCode", "HID0101");
        query.put("status", 0);
        json.put("query", query);
        String url = "https://hytapiv2.cd120.com/cloud/hosplatcustomer/call/appointment/appointmentModel/selAppointmentRecord";
        HttpResponse response = HutoolUtil.sendPost(url, token, json);
        RecordDTO result = HutoolUtil.parseJsonResponse(response, RecordDTO.class);
        List<ContentDTO> contentDTOS = result.getData().getContent();
        if (CollUtil.isNotEmpty(contentDTOS)) {
            contentDTOS.stream().filter(contentDTO -> contentDTO.getCardId().equals(appointmentTasksDO.getCardId()) && contentDTO.getSysScheduleId().equals(appointmentTasksDO.getSysScheduleId())).forEach(contentDTO -> {
                appointmentTasksDO.setTaskStatus(TaskStatus.APPOINTMENT_SUCCESSFUL.getCode());
                appointmentTasksDO.setUpdateTime(new Date());
                updateById(appointmentTasksDO);
            });
        }

        return contentDTOS;
    }

    @Override
    public void copy(Integer id) {
        AppointmentTasksDO appointmentTasksDO = getById(id);
        AppointmentTasksDO appointmentTasksDO1 = new AppointmentTasksDO();
        appointmentTasksDO1.setAppointmentPerson(appointmentTasksDO.getAppointmentPerson());
        appointmentTasksDO1.setCustomer(appointmentTasksDO.getCustomer());
        appointmentTasksDO1.setProcessor(appointmentTasksDO.getProcessor());
        appointmentTasksDO1.setAppointmentPhone(appointmentTasksDO.getAppointmentPhone());
        appointmentTasksDO1.setToken(appointmentTasksDO.getToken());
        appointmentTasksDO1.setCreateTime(new Date());
        appointmentTasksDO1.setTaskStatus(TaskStatus.PENDING_CONFIGURATION.getCode());
        appointmentTasksDO1.setStatus(null);
        save(appointmentTasksDO1);
    }

    @Override
    public String checkToken(Integer id) {
        AppointmentTasksDO appointmentTasksDO = getById(id);
        String token = appointmentTasksDO.getToken();
        JSONObject json = new JSONObject();
        JSONObject query = new JSONObject();
        json.put("asc", "true");
        json.put("pageNum", 1);
        json.put("pageSize", 200);
        query.put("appCode", "HXGYAPP");
        query.put("channelCode", "PATIENT_IOS");
        query.put("hospitalCode", "HID0101");
        query.put("status", 0);
        json.put("query", query);
        String url = "https://hytapiv2.cd120.com/cloud/hosplatcustomer/call/appointment/appointmentModel/selAppointmentRecord";
        try {
            HttpResponse response = HutoolUtil.sendPost(url, token, json);
            RecordDTO result = HutoolUtil.parseJsonResponse(response, RecordDTO.class);
            List<ContentDTO> contentDTOS = result.getData().getContent();
            if (Objects.isNull(contentDTOS)) {
                return "token失效";
            }
            return "token有效";
        } catch (Exception e) {
            log.info("发生异常：" + e.getMessage());
            return "token失效";
        }


    }


    @Override
    public void autoSureAppointment(AppointmentTasksDO appointmentTasksDO) {
        log.info("开始自动提交" + appointmentTasksDO.getDocName());
        if (appointmentTasksDO.getTaskStatus().equals(TaskStatus.PENDING_INITIATION.getCode())) {
            QueryWrapper<ImageDataDO> wrapper = new QueryWrapper<>();
            wrapper.eq("task_id", appointmentTasksDO.getId());
            wrapper.eq("is_used", 0);
            List<ImageDataDO> imageDataDOS = imageDataService.list(wrapper);
            if (CollUtil.isNotEmpty(imageDataDOS)) {
                for (ImageDataDO imageDataDO : imageDataDOS) {
                    subscribe(appointmentTasksDO, imageDataDO);
                    try {
                        Thread.sleep(SECONDS); // 0.5秒钟，单位为毫秒
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
//                int size = imageDataDOS.size();
//                int partSize = size / 4;
//                int remainder = size % 4;
//
//                for (int part = 0; part < 4; part++) {
//                    int startIndex = part * partSize + Math.min(part, remainder);
//                    int endIndex = startIndex + partSize + (part < remainder ? 1 : 0);
//
//                    // 执行当前部分的操作
//                    for (int i = startIndex; i < endIndex; i++) {
//                        ImageDataDO imageDataDO = imageDataDOS.get(i);
//                        subscribe(appointmentTasksDO, imageDataDO);
//                    }
//
//                    // 打印日志，表示当前部分已执行完
//                    log.info("完成第 " + (part + 1) + " 部分的提交，索引范围: [" + startIndex + ", " + endIndex + ")");
//
//                    // 在执行完每一部分后（除了最后一部分）都等待1秒
//                    if (part < 3) {
//                        try {
//                            Thread.sleep(1000); // 1秒钟，单位为毫秒
//                        } catch (InterruptedException e) {
//                            e.printStackTrace();
//                        }
//                    }
//                }
            }
        }
    }


    private void subscribe(AppointmentTasksDO appointmentTasksDO, ImageDataDO imageDataDO) {
        log.info("开始自动提交验证码" + appointmentTasksDO.getDocName() + imageDataDO.getId());
        imageDataDO.setIsUsed(1);
        imageDataService.updateById(imageDataDO);
        appointmentTasksDO.setTaskStatus(TaskStatus.APPOINTMENT_FAILED.getCode());
        appointmentTasksDO.setUpdateTime(new Date());
        updateById(appointmentTasksDO);
        String token = appointmentTasksDO.getToken();
        JSONObject json = new JSONObject();
        json.put("appCode", "HXGYAPP");
        json.put("appointmentType", "1");
        json.put("cardId", appointmentTasksDO.getCardId());
        json.put("channelCode", "PATIENT_IOS");
        json.put("hospitalCode", "HID0101");
        json.put("sysScheduleId", appointmentTasksDO.getSysScheduleId());
        json.put("type", "WEB");
        json.put("verifyCode", imageDataDO.getImageCode());
        json.put("channelElderCode", "PATIENT_IOS");
        json.put("imageId", imageDataDO.getBizSeq());
        json.put("encrypt", SecretUtil.encrypt(SecretUtil.getImageId(imageDataDO.getBizSeq())));
        log.info(appointmentTasksDO.getId() + "请求参数：" + json.toJSONString());
        String url = "https://hytapiv2.cd120.com/cloud/hosplatcustomer/call/appointment/appointmentModel/sureAppointment";
        ApiLogDO apiLogDO = addApiLog(appointmentTasksDO, "华医通提交预约-自动", url, json.toJSONString());
        ExecutorService executorService = Executors.newSingleThreadExecutor();
        executorService.execute(() -> {
            try {
                HttpResponse response = HutoolUtil.sendPost(url, token, json);
                log.info("返回response：" + response);
                SureAppointmentDTO result = HutoolUtil.parseJsonResponse(response, SureAppointmentDTO.class);
                // 处理返回结果
                log.info("返回参数：" + result);
                updateApiLog(appointmentTasksDO, apiLogDO, response.body());
            } catch (Exception e) {
                // 处理异常
                updateApiLog(appointmentTasksDO, apiLogDO, e.getMessage());
                log.info("发生异常：" + e.getMessage());
            }
        });
        executorService.shutdown();
    }


    @Override
    public void appointmentCancelOrBack(BackDTO backDTO) {
        AppointmentTasksDO appointmentTasksDO = getById(backDTO.getId());
        String token = appointmentTasksDO.getToken();
        JSONObject json = new JSONObject();
        json.put("sysAppointmentId", backDTO.getSysAppointmentId());
        json.put("types", "1");
        json.put("appCode", "HXGYAPP");
        json.put("cancleType", "4");
        json.put("channelCode", "PATIENT_IOS");
        json.put("refundType", "0");
        log.info(backDTO.getId() + "请求参数：" + json.toJSONString());
        String url = "https://hytapiv2.cd120.com/cloud/hosplatcustomer/call/appointment/appointmentModel/appointmentCancelOrBack";
        HttpResponse response;
        try {
            response = HutoolUtil.sendPost(url, token, json);
            log.info("返回参数：" + response.body());
        } catch (Exception e) {
            log.info("发生异常：" + e.getMessage());
            throw new RuntimeException(e);
        }
    }

    private COSClient getCosClient() {
        COSCredentials cred = new BasicCOSCredentials(SECRET_ID, SECRET_KEY);
        Region region = new Region("ap-chengdu");
        ClientConfig clientConfig = new ClientConfig(region);
        clientConfig.setHttpProtocol(HttpProtocol.https);
        return new COSClient(cred, clientConfig);
    }

    @Override
    public String appointmentToPay(BackDTO backDTO) {
        String token = getTokenFromDTO(backDTO);
        JSONObject json = buildJsonObject(backDTO);
        logRequestParameters(backDTO, json);
        try {
            HttpResponse postResponse = sendPostRequest(json, token);
            ToPayDTO result = HutoolUtil.parseJsonResponse(postResponse, ToPayDTO.class);
            HttpResponse getResponse = sendGetRequest(result.getData(), token);
            String qrcodeContent = parseQrCodeContent(getResponse);
            return generateQrCodeImage(qrcodeContent);
        } catch (Exception e) {
            log.error("Exception occurred: ", e);
            throw new RuntimeException(e);
        }
    }

    private String getTokenFromDTO(BackDTO backDTO) {
        AppointmentTasksDO appointmentTasksDO = getById(backDTO.getId());
        return appointmentTasksDO.getToken();
    }

    private JSONObject buildJsonObject(BackDTO backDTO) {
        JSONObject json = new JSONObject();
        json.put("appCode", APP_CODE);
        json.put("channelCode", "");
        json.put("hospitalCode", HOSPITAL_CODE);
        json.put("openId", "");
        json.put("sysAppointmentId", backDTO.getSysAppointmentId());
        json.put("sysOrderTypeId", "");
        json.put("userId", "");
        return json;
    }

    private void logRequestParameters(BackDTO backDTO, JSONObject json) {
        log.info("{} Request Parameters: {}", backDTO.getId(), json.toJSONString());
    }

    private HttpResponse sendPostRequest(JSONObject json, String token) {
        String url = "https://hytapiv2.cd120.com/cloud/hosplatcustomer/call/appointment/appointmentModel/appointmentToPay";
        return HutoolUtil.sendPost(url, token, json);
    }

    private HttpResponse sendGetRequest(PayDTO payDTO, String token) {
        String getUrl = String.format("https://hxgyapiv2.cd120.info/cloud/paygateway/ccbpay/getQRCode?dealSeq=%s&bizSysSeq=%s", payDTO.getDealSeq(), payDTO.getBizSysSeq());
        return HutoolUtil.sendGet(getUrl, token);
    }

    private String parseQrCodeContent(HttpResponse response) {
        CodeDTO codeDTO = HutoolUtil.parseJsonResponse(response, CodeDTO.class);
        log.info("Payment URL: {}", codeDTO.getData());
        return codeDTO.getData();
    }

    private String generateQrCodeImage(String content) {
        COSClient cosClient = getCosClient();
        GenerateQrcodeRequest request = new GenerateQrcodeRequest();
        request.setBucketName(BUCKET_NAME);
        request.setQrcodeContent(content);
        request.setWidth("200");
        request.setMode("0");
        String imageBase64 = cosClient.generateQrcode(request);
        log.info("QrCode Image Base64: {}", imageBase64);
        return imageBase64;
    }


    @Override
    public List<ScheduleDTO> selWeekScheduleTwo(ScheduleRequestVO scheduleRequestVO) {
        AppointmentTasksDO appointmentTasksDO = getById(scheduleRequestVO.getId());
        String token = appointmentTasksDO.getToken();
        JSONObject json = new JSONObject();
        // 格式化日期为字符串
        SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd");
        json.put("deptCategoryCode", appointmentTasksDO.getDeptCategoryCode());
        json.put("hospitalAreaCode", "HID0101");
        json.put("hospitalCode", "HID0101");
        json.put("scheduleDateEnd", formatter.format(appointmentTasksDO.getTreatmentDate()));
        json.put("scheduleDateStart", formatter.format(appointmentTasksDO.getTreatmentDate()));
        json.put("channelCode", "PATIENT_IOS");
        json.put("appCode", "HXGYAPP");
        json.put("weekScheduleReqBoVos", scheduleRequestVO.getWeekScheduleReqBoVos());
        log.info("请求参数：" + json.toJSONString());
        String url = "https://hytapiv2.cd120.com/cloud/hosplatcustomer/call/appointment/doctorListModel/selWeekScheduleTwo";
        ApiLogDO apiLogDO = addApiLog("华医通查询医生一周的排班", url, json.toJSONString());
        HttpResponse response;
        List<ScheduleDTO> scheduleDTOS;
        try {
            response = HutoolUtil.sendPost(url, token, json);
            ScheduleResponseDTO result = HutoolUtil.parseJsonResponse(response, ScheduleResponseDTO.class);
            scheduleDTOS = result.getData();
            if (CollUtil.isNotEmpty(scheduleDTOS)) {
                List<ScheduleDTO> filteredList = scheduleDTOS.stream().filter(scheduleDTO -> scheduleDTO.getStatus() != 3).collect(Collectors.toList());
                if (CollUtil.isNotEmpty(filteredList)) {
                    filteredList.forEach(scheduleDTO -> {
                        String sysScheduleId = scheduleDTO.getSourceItemsRespVos().getSysScheduleId();
                        int scheduleRange = scheduleDTO.getSourceItemsRespVos().getScheduleRange();
                        QueryWrapper<AppointmentScheduleDO> wrapper = new QueryWrapper<>();
                        wrapper.eq("sys_schedule_id", sysScheduleId);
                        wrapper.eq("schedule_range", scheduleRange);
                        AppointmentScheduleDO departmentCategoryDO = appointmentScheduleService.getOne(wrapper);
                        if (Objects.isNull(departmentCategoryDO)) {
                            departmentCategoryDO = ConvertUtils.beanCopy(scheduleDTO, AppointmentScheduleDO.class);
                            BeanUtil.copyProperties(scheduleDTO.getSourceItemsRespVos(), departmentCategoryDO);
                            appointmentScheduleService.save(departmentCategoryDO);
                        }
                    });
                }
                QueryWrapper<AppointmentScheduleDO> wrapper = new QueryWrapper<>();
                wrapper.eq("schedule_date", formatter.format(appointmentTasksDO.getTreatmentDate()));
                wrapper.eq("schedule_range", appointmentTasksDO.getTreatmentRange());
                wrapper.eq("dept_code", appointmentTasksDO.getDeptCode());
                wrapper.eq("doctor_id", appointmentTasksDO.getDoctorId());
                AppointmentScheduleDO departmentCategoryDO = appointmentScheduleService.getOne(wrapper);
                if (!Objects.isNull(departmentCategoryDO)) {
                    appointmentTasksDO.setTaskStatus(TaskStatus.PENDING_INITIATION.getCode());
                    appointmentTasksDO.setSysScheduleId(departmentCategoryDO.getSysScheduleId());
                } else {
                    appointmentTasksDO.setTaskStatus(TaskStatus.RETRIEVAL_FAILED.getCode());
                }
            } else {
                appointmentTasksDO.setTaskStatus(TaskStatus.RETRIEVAL_FAILED.getCode());
            }
            updateById(appointmentTasksDO);
        } catch (Exception e) {
            log.info("发生异常：" + e.getMessage());
            throw new RuntimeException(e);
        }
        updateApiLog(appointmentTasksDO, apiLogDO, response.body());
        return scheduleDTOS;
    }

    @Override
    public ImageDataDO getImageCode(Integer id) {
        AppointmentTasksDO appointmentTasksDO = getById(id);
        ImageDataDO imageDataDO = new ImageDataDO();
        String token = appointmentTasksDO.getToken();
        JSONObject json = new JSONObject();
        json.put("type", "WEB");
        log.info("请求参数：" + json.toJSONString());
        String url = "https://hxgyapiv2.cd120.info/cloud/hosplatcustomer/customer/image/getimagecode";
        ApiLogDO apiLogDO = addApiLog("华医通获取验证码", url, json.toJSONString());
        try {
            HttpResponse response = HutoolUtil.sendPost(url, token, json);
            ImageCodeDTO result = HutoolUtil.parseJsonResponse(response, ImageCodeDTO.class);
            ImageDTO imageDTO = result.getData();
            if (!Objects.isNull(imageDTO)) {
                String code = ImageUtils.recognition(imageDTO.getImageData());
                imageDataDO = ConvertUtils.beanCopy(imageDTO, ImageDataDO.class);
                imageDataDO.setCreateTime(new Date());
                imageDataDO.setImageCode(code);
                imageDataDO.setTaskId(id);
                imageDataDO.setIsUsed(0);
                imageDataService.save(imageDataDO);
            }
            updateApiLog(appointmentTasksDO, apiLogDO, response.body());
        } catch (Exception e) {
            log.info("发生异常：" + e.getMessage());
            throw new RuntimeException(e);
        }

        return imageDataDO;
    }

    private ApiLogDO addApiLog(String name, String url, String json) {
        ApiLogDO apiLogDO = new ApiLogDO();
        apiLogDO.setName(name);
        apiLogDO.setUrl(url);
        apiLogDO.setRequestParams(json);
        apiLogDO.setCreateTime(new Date());
        apiLogService.save(apiLogDO);
        return apiLogDO;
    }

    private ApiLogDO addApiLog(AppointmentTasksDO appointmentTasksDO, String name, String url, String json) {
        ApiLogDO apiLogDO = new ApiLogDO();
        apiLogDO.setTaskId(appointmentTasksDO.getId());
        apiLogDO.setName(name);
        apiLogDO.setUrl(url);
        apiLogDO.setRequestParams(json);
        apiLogDO.setCreateTime(new Date());
        apiLogService.save(apiLogDO);
        return apiLogDO;
    }

    private void updateApiLog(AppointmentTasksDO appointmentTasksDO, ApiLogDO apiLogDO, String response) {
        apiLogDO.setTaskId(appointmentTasksDO.getId());
        apiLogDO.setResponseParams(response);
        apiLogDO.setUpdateTime(new Date());
        apiLogService.updateById(apiLogDO);
    }


}
